import shelve
import sys
sys.path.append("/home/cyw/projects/function_sim_project/function_sim/")
sys.path.append("/home/cyw/projects/function_sim_project/basic_script")
from functionSim_train import functionModelWarpper
from easySample import easySample
from tqdm import tqdm
import torch
from functionSim_config import *
import time

PAIR_NAME="test"
FUNCTIONSIM_ZERO=r"/home/cyw/projects/function_sim_project/all_data/models/functionSim_zero_model.pth"
FUNTIONSIM_HETE=r"/home/cyw/projects/function_sim_project/all_data/models/functionSim_with_hete_model.pth"
FUNCTIONSIM=r"/home/cyw/projects/function_sim_project/all_data/models/functionSim_model_cross_edge_best_4_8.pth"
threshold=0.5
a=easySample()

def get_model_and_trainer(modelName):
    if modelName=="functionSim":
        model=torch.load(FUNCTIONSIM)
        modelTrainer=functionModelWarpper(model)
    elif modelName=="functionSim_with_hete":
        model=torch.load(FUNTIONSIM_HETE)
        modelTrainer=functionModelWarpper(model)
    elif modelName=="functionSim_zero":
        model=torch.load(FUNCTIONSIM_ZERO)
        modelTrainer=functionModelWarpper(model)
    return model,modelTrainer

def get_pair_res(pairInf,pairName,trainer):
    """
        获得模型计算的样本对相似值
    """
    
    dataloader=trainer.get_model_dataloader(pairInf,pairName,False,False)
    print("样本加载完成")
    a = time.time()
    res=trainer.get_model_score(dataloader)
    b = time.time()
    print("计算完成:耗时{}".format(b-a))
    return res

def get_pair(dataName="test"):
    """
        获得用于测试的样本对，默认test样本集
    """
    testPair=[]
    with shelve.open("/home/cyw/projects/function_sim_project/all_data/pair_infs/pair_infs") as file:
        if dataName=="valid":
            testPair=file["validPair"]
        elif dataName=="test":
            testPair=file["testPair"]
        else:
            raise "数据集不支持"
    return testPair


def gene_all_infs(pairInf,res,save_name):
    """
        将数据汇总，进行处理生成需要的格式
        误报  FP 负类别的样本被错误地预测为正类别。，漏报
    """
    ans={}
    FN = {}
    FP = {}
    pair_res={}
    for i in tqdm(range(len(res))):
        name="{}--{}".format(pairInf[i][0],pairInf[i][1])
        tar=[res[i]]
        tar.extend(pairInf[i])
        # #这里用来查看样本的长度
        tar.append(str(len(a.get_sample(pairInf[i][0],"functionSim")["adj"])))
        tar.append(str(len(a.get_sample(pairInf[i][1],"functionSim")["adj"])))
        if(res[i]>=0.5 and pairInf[i][2]==-1):
            FP[name]=tar
        elif(res[i]<0.5 and pairInf[i][2]==1):
            FN[name]=tar      
        pair_res[name]=tar
    ans["fp"]=FP
    ans["fn"]=FN
    ans["pair_res"] = pair_res
    with shelve.open("/home/cyw/projects/function_sim_project/all_data/indicators/fpAndFn/{}_threshold".format(save_name)) as file:
        file["ans"] = ans
    return ans

def get_all_infs(save_name):
    with shelve.open("/home/cyw/projects/function_sim_project/all_data/indicators/fpAndFn/{}_threshold".format(save_name)) as file:
        ans = file["ans"]
    return ans

def show_pair_differ(modelName,modelName1):
    """
        不同模型之间样本对的对比
        前者是好的,或者是坏的
    """
    print("正在生成不同模型间的样本对")
    res={}
    for name in modelList:
        res[name]=get_all_infs(name)

    pair_total={}
    for id in res["functionSim"]["pair_res"].keys():
        tempData=[]
        tempData.append(res["functionSim"]["pair_res"][id][4]+"-"+res["functionSim"]["pair_res"][id][6])
        tempData.append(res["functionSim"]["pair_res"][id][5]+"-"+res["functionSim"]["pair_res"][id][7])
        for name in modelList:
            tempData.append(res[name]["pair_res"][id][0])
        pair_total[id]=tempData
    
    print("------------------------fp-------------------------")
    data1=[]
    for id in res[modelName1]["fp"]:
        if id not in res[modelName]['fp']:
            print(id+ "  " +str(pair_total[id]))
            data1.append(pair_total[id])   
    print("长度为{}".format(len(data1)))
    print("------------------------fn-------------------------")
    data2=[]
    for id in res[modelName1]["fn"]:
        if id not in res[modelName]['fn']:
            print(id+ "  " +str(pair_total[id]))
            data2.append(pair_total[id])
    print("长度为{}".format(len(data2)))


if __name__ =="__main__":
    modelList=["functionSim","functionSim_with_hete","functionSim_zero"]
    # print("注意切换配置信息保持一致，加载模型需要和配置信息一致，包括跨图组件，异质组件，跨图方法")
    # modelname=modelList[0]
    # pairInf=get_pair(PAIR_NAME)
    # print("{:25}{:>8}{:>8}".format("model_name","fp","fn"))
    # # 生成训练所需的样本对数据
    # model,trainer = get_model_and_trainer(modelname) 
    # model.to(device)
    # print("model 加载完成")
    # pairRes = get_pair_res(pairInf,PAIR_NAME,trainer)
    # gene_all_infs(pairInf,pairRes,modelname)
    # res=get_all_infs(modelname)
    # print("{:25}{:>8}{:>8}".format(modelname,len(res['fp']),len(res['fn'])))

    # show_pair_differ(modelList[0],modelList[1])
    # show_pair_differ(modelList[1],modelList[2])
    show_pair_differ(modelList[0],modelList[2])